﻿using System;
using System.Data;
using System.Drawing;
using System.Management;
using System.Windows.Forms;
using AForge.Video.DirectShow;

namespace ViewCam
{
    class ViewCamHelper : IDisposable
    {
        #region Declarations
        /// <summary>
        /// The webcam
        /// </summary>
        private FilterInfoCollection webcam;
        /// <summary>
        /// The config
        /// </summary>
        private Config config;
        /// <summary>
        /// The config table
        /// </summary>
        private DataTable configTable = new DataTable();
        #endregion
                
        #region Public Methods
        /// <summary>
        /// Loads the status message.
        /// </summary>
        /// <param name="strMessage">The STR message.</param>
        /// <param name="lblStatus">The LBL status.</param>
        public void LoadStatusMessage(string strMessage, ToolStripStatusLabel lblStatus)
        {
            lblStatus.Text = strMessage; 
        }

        /// <summary>
        /// Loads the web cam.
        /// </summary>
        /// <param name="cmbWebCam">The CMB web cam.</param>
        public void LoadWebCam(ToolStripComboBox cmbWebCam)
        {
            webcam = new FilterInfoCollection(FilterCategory.VideoInputDevice);
            LoadWebCamCombo(webcam, cmbWebCam);
        }

        /// <summary>
        /// Removes the web cam.
        /// </summary>
        /// <param name="cmbWebCam">The CMB web cam.</param>
        /// <param name="cmbCamName">Name of the CMB cam.</param>
        public void RemoveWebCam(ToolStripComboBox cmbWebCam, string cmbCamName)
        {
            cmbWebCam.Items.Remove(cmbCamName);
            cmbWebCam.Text = "";
        }

        /// <summary>
        /// Closes all child forms.
        /// </summary>
        /// <param name="main">The main.</param>
        public void CloseAllChildForms(Form main)
        {
            try
            {
                foreach (CameraForm camForm in main.MdiChildren)
                {
                    camForm.Close();
                    camForm.Shutdown();
                }
                
            }
            catch (Exception)
            { }

            try
            {
                foreach (SettingsForm settForm in main.MdiChildren)
                {
                    settForm.Close();
                }
            }
            catch (Exception)
            { }

            try
            {
                foreach (CameraIPForm camIPForm in main.MdiChildren)
                {
                    camIPForm.Close();
                    camIPForm.CloseCurrentVideoSource();
                    camIPForm.Shutdown();
                }
            }
            catch (Exception)
            { }
        }

        /// <summary>
        /// Shares the folder.
        /// </summary>
        /// <param name="FolderPath">The folder path.</param>
        /// <param name="ShareName">Name of the share.</param>
        /// <param name="Description">The description.</param>
        public void ShareFolder(string FolderPath, string ShareName, string Description)
        {
            if (FolderPath != "" & ShareName != "" & Description != "")
                SetFolderToShared(FolderPath, ShareName, Description);
        }

        /// <summary>
        /// Enables the tool tip.
        /// </summary>
        /// <param name="message">The message.</param>
        /// <param name="objct">The objct.</param>
        /// <param name="toolTip">The tool tip.</param>
        public void EnableToolTip(string message, Control objct, ToolTip toolTip)
        {
            toolTip.Active = true;
            toolTip.ToolTipTitle = "View Cam";
            toolTip.ToolTipIcon = ToolTipIcon.Info;
            toolTip.SetToolTip(objct, message);
        }

        /// <summary>
        /// Gets the config settings.
        /// </summary>
        /// <param name="key">The key.</param>
        /// <param name="lblStatus">The LBL status.</param>
        /// <returns></returns>
        public string GetConfigSettings(string key, ToolStripLabel lblStatus)
        {
            config = new Config();
            string value;
            value = "";
            try
            {
                config.ReadXml("config.xml");
                DataRow data = config.Options.Select("Key = '" + key + "'")[0];
                value = data[1].ToString();
            }
            catch (Exception ex)
            {
                if (ex.Message != null)
                { lblStatus.Text = "View Cam Settings has not yet been set."; }
            }
            return value;
        }

        /// <summary>
        /// Saves the config settings.
        /// </summary>
        /// <param name="key">The key.</param>
        /// <param name="cntrl">The CNTRL.</param>
        public void SaveConfigSettings(string key, Control cntrl)
        {
            DataTable configTbl = null;
            DataRow configRow = null;

            if (configTable.Rows.Count > 0)
            {
                configTbl = configTable;
            }
            else
            {
                configTbl = CreateConfigTable();
            }
            
            configRow = configTbl.NewRow();

            try
            {
                configRow["Key"] = key;
                configRow["Value"] = cntrl.Text;
                configTbl.Rows.Add(configRow);
            }
            catch (Exception ex)
            {
                if (ex.Message != null)
                { configRow = null; }
            }

            configRow = null;
            configTable = configTbl;
        }

        /// <summary>
        /// Writes the config settings.
        /// </summary>
        public void WriteConfigSettings()
        {
            WriteConfig(configTable);
        }

        /// <summary>
        /// Tests the beep sound.
        /// </summary>
        /// <param name="freq">The freq.</param>
        /// <param name="dura">The dura.</param>
        public void TestBeepSound(Int32 freq, Int32 dura)
        {
            System.Console.Beep(freq, dura);
        }

        /// <summary>
        /// Hexes to color.
        /// </summary>
        /// <param name="hexColor">Color of the hex.</param>
        /// <returns></returns>
        public Color HexToColor(string hexColor)
        {
            Color color;
            color = ColorTranslator.FromHtml("#" + hexColor);
            return color;
        }

        /// <summary>
        /// Sets the color of the theme.
        /// </summary>
        /// <param name="lblStatus">The LBL status.</param>
        /// <returns></returns>
        public Color SetThemeColor(ToolStripLabel lblStatus)
        {
            Color backColor;

            try
            {
                backColor = HexToColor(GetConfigSettings("Theme", lblStatus));
            }
            catch (Exception)
            {
                backColor = Color.White;
            }
            
            return backColor;
        }

        /// <summary>
        /// Loads the form.
        /// </summary>
        /// <param name="mainForm">The main form.</param>
        /// <param name="backColor">Color of the back.</param>
        public void LoadForm(Form mainForm, Color backColor)
        {
            MdiClient ctlMDI;
            foreach (Control ctl in mainForm.Controls)
            {
                try
                {
                    ctlMDI = (MdiClient)ctl;
                    ctlMDI.BackColor = backColor;
                }
                catch (Exception)
                { }
            }
        }

        /// <summary>
        /// Verifies the config file.
        /// </summary>
        /// <returns></returns>
        public string VerifyConfigFile()
        {
            string test = VerifyFile();
            return test;
        }
        #endregion

        #region Private Methods
        /// <summary>
        /// Loads the web cam combo.
        /// </summary>
        /// <param name="ficWebCam">The fic web cam.</param>
        /// <param name="cmbWebCam">The CMB web cam.</param>
        private void LoadWebCamCombo(FilterInfoCollection ficWebCam, ToolStripComboBox cmbWebCam)
        {
            if (ficWebCam != null)
            {
                cmbWebCam.Items.Clear();
                for (int i = 0; i < ficWebCam.Count; i++)
                {
                    cmbWebCam.Items.Add(ficWebCam[i].Name);
                }
            }
        }

        /// <summary>
        /// Sets the folder to shared.
        /// </summary>
        /// <param name="FolderPath">The folder path.</param>
        /// <param name="ShareName">Name of the share.</param>
        /// <param name="Description">The description.</param>
        private void SetFolderToShared(string FolderPath, string ShareName, string Description)
        {
            try
            {
                // Calling Win32_Share class to create a shared folder
                ManagementClass managementClass = new ManagementClass("Win32_Share");
                // Get the parameter for the Create Method for the folder
                ManagementBaseObject inParams = managementClass.GetMethodParameters("Create");
                ManagementBaseObject outParams;
                // Assigning the values to the parameters
                inParams["Description"] = Description;
                inParams["Name"] = ShareName;
                inParams["Path"] = FolderPath;
                inParams["Type"] = 0x0;
                // Finally Invoke the Create Method to do the process
                outParams = managementClass.InvokeMethod("Create", inParams, null);
                // Validation done here to check sharing is done or not
                if ((uint)(outParams.Properties["ReturnValue"].Value) != 0)
                    MessageBox.Show("Folder might be already in share or unable to share.", "View Cam");
                else
                    MessageBox.Show("Folder shared to network.", "View Cam");
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message, "View Cam");
            } 
        }

        /// <summary>
        /// Creates the config table.
        /// </summary>
        /// <returns></returns>
        private DataTable CreateConfigTable()
        {
            DataTable configtable = new DataTable();

            configtable.Columns.Add("Key");
            configtable.Columns.Add("Value");

            return configtable;
        }

        /// <summary>
        /// Creates the IP cam table.
        /// </summary>
        /// <returns></returns>
        private DataTable CreateIPCamTable()
        {
            DataTable ipCamtable = new DataTable();

            ipCamtable.Columns.Add("id");
            ipCamtable.Columns.Add("name");
            ipCamtable.Columns.Add("description");
            ipCamtable.Columns.Add("provider");
            ipCamtable.Columns.Add("source");
            ipCamtable.Columns.Add("login");
            ipCamtable.Columns.Add("password");
            ipCamtable.Columns.Add("interval");

            return ipCamtable;
        }

        /// <summary>
        /// Writes the config.
        /// </summary>
        /// <param name="tblConfig">The TBL config.</param>
        private void WriteConfig(DataTable tblConfig)
        {
            config = new Config();
            
            if (tblConfig.Rows.Count > 0)
                {
                    for (int i = 0; i < (tblConfig.Rows.Count); i++)
                    {
                        try
                        {
                            DataRow data = this.config.Options.Select("Key = '" + tblConfig.Rows[i]["Key"].ToString() + "'")[0];
                            data[1] = tblConfig.Rows[i]["Value"].ToString();
                        }
                        catch (Exception)
                        {
                            this.config.Options.AddOptionsRow(tblConfig.Rows[i]["Key"].ToString(), tblConfig.Rows[i]["Value"].ToString());
                        }
                        
                    }
                }
            this.config.WriteXml("config.xml");
        }

        /// <summary>
        /// Verifies the file.
        /// </summary>
        /// <returns></returns>
        private string VerifyFile()
        {
            string test = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);
            return test;
        }
        #endregion

        #region Dispose
        /// <summary>
        /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
        /// </summary>
        public void Dispose()
        {
            configTable = null;
            config = null;
            webcam = null;
            GC.SuppressFinalize(this);
        }
        #endregion
    }
}